/*
 * $Id: DisciplinePlanningItemDao.java 1678 2011-08-25 10:41:01Z abie $
 * 
 * Copyright (c) 2001-2008 Accentrix Company Limited. All Rights Reserved.
 * 
 * Accentrix Company Limited. ("Accentrix") retains copyright on all text, source
 * and binary code contained in this software and documentation. Accentrix grants
 * Licensee a limited license to use this software, provided that this copyright
 * notice and license appear on all copies of the software. The software source
 * code is provided for reference purposes only and may not be copied, modified 
 * or distributed.
 * 
 * THIS SOFTWARE AND DOCUMENTATION ARE PROVIDED "AS IS," WITHOUT ANY WARRANTY OF
 * ANY KIND UNLESS A SEPARATE WARRANTIES IS PURCHASED FROM ACCENTRIX AND REMAINS
 * VALID.  ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND WARRANTIES,
 * INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
 * PURPOSE OR NON-INFRINGEMENT, ARE HEREBY EXCLUDED. ACCENTRIX SHALL NOT BE LIABLE
 * FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF USING OR MODIFYING THE
 * SOFTWARE OR ITS DERIVATIVES.
 * 
 * IN NO EVENT WILL ACCENTRIX BE LIABLE FOR ANY LOST REVENUE, PROFIT OR DATA, OR
 * FOR DIRECT, INDIRECT, SPECIAL, CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES,
 * HOWEVER CAUSED AND REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE
 * USE OF OR INABILITY TO USE SOFTWARE, EVEN IF ACCENTRIX HAS BEEN ADVISED OF THE
 * POSSIBILITY OF SUCH DAMAGES.
 */
package com.lightsaber.trade.cloth.dao.planning;

import java.util.List;

import org.hibernate.Query;
import org.hibernate.criterion.Order;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Component;

import com.lightsaber.trade.core.dao.BaseDao;
import com.lightsaber.trade.cloth.entity.category.CategoryNode;
import com.lightsaber.trade.cloth.entity.planning.DisciplinePlanningItem;
import com.lightsaber.trade.cloth.entity.planning.Level1Planning;

@Component
public class DisciplinePlanningItemDao extends BaseDao<DisciplinePlanningItem, String> {

    private static final Logger log = LoggerFactory.getLogger(DisciplinePlanningItemDao.class);

    public long countByPlanningAndCategoryNode(final Level1Planning level1Planning,
            final CategoryNode categoryNode) {

        eq("level1Planning", level1Planning);
        eq("categoryNode", categoryNode);

        return count();
    }

    public DisciplinePlanningItem findUnique(final Level1Planning level1Planning,
            final CategoryNode categoryNode, final Integer planYear, final String discipline,
            final String fundingMode) {

        eq("level1Planning", level1Planning);
        eq("categoryNode", categoryNode);

        eq("discipline", discipline);
        eq("fundingMode", fundingMode);
        eq("planYear", planYear);

        return unique();
    }

    public DisciplinePlanningItem findByAllRestriction(final String level1PlanningId,
            final String categoryNodeId, final Integer planYear, final String discipline,
            final String fundingMode) {

        eq("level1Planning.id", level1PlanningId);
        eq("categoryNode.id", categoryNodeId);

        eq("discipline", discipline);
        eq("fundingMode", fundingMode);
        eq("planYear", planYear);

        return unique();
    }

    public List<DisciplinePlanningItem> findByPlanAndNode(final Level1Planning level1Planning,
            final CategoryNode categoryNode) {

        eq("level1Planning", level1Planning);
        eq("categoryNode", categoryNode);

        addOrder(Order.asc("discipline"));
        addOrder(Order.asc("fundingMode"));
        addOrder(Order.asc("planYear"));

        return list();
    }

    public List<DisciplinePlanningItem> findByPlanAndNodeAndYear(
            final Level1Planning level1Planning, final CategoryNode categoryNode,
            final Integer planYear) {

        eq("level1Planning", level1Planning);
        eq("categoryNode", categoryNode);
        eq("planYear", planYear);

        return list();
    }

    public long totalPlanedPlacesByPlanAndNodeAndYear(final Level1Planning level1Planning,
            final CategoryNode categoryNode, final Integer planYear) {

        String hql = "select sum(ditem.plannedPlaces) from DisciplinePlanningItem as ditem "
                + "where ditem.level1Planning=:level1Planning "
                + "and ditem.categoryNode=:categoryNode and ditem.planYear=:planYear";

        Query q = this.createQuery(hql);
        q.setParameter("categoryNode", categoryNode);
        q.setParameter("level1Planning", level1Planning);
        q.setParameter("planYear", planYear);

        return (Long) q.uniqueResult();
    }

    public long totalPlanedPlacesByLevel1AndNodeAndYearAndDiscipline(
            final Level1Planning level1Planning, final CategoryNode categoryNode,
            final Integer planYear, final String discipline) {

        String hql = "select sum(ditem.plannedPlaces) from DisciplinePlanningItem as ditem "
                + "where ditem.level1Planning=:level1Planning "
                + "and ditem.categoryNode=:categoryNode and ditem.planYear=:planYear "
                + " and ditem.discipline=:discipline";

        Query q = this.createQuery(hql);
        q.setParameter("categoryNode", categoryNode);
        q.setParameter("level1Planning", level1Planning);
        q.setParameter("planYear", planYear);
        q.setParameter("discipline", discipline);

        List list = q.list();
        if (list.isEmpty())
            return 0;
        else if (list.get(0) == null) {
            return 0;
        } else
            return (Long) list.get(0);

    }

    public long countByPlanAndNodeAndYear(final Level1Planning level1Planning,
            final CategoryNode categoryNode, final Integer planYear) {

        eq("level1Planning", level1Planning);
        eq("categoryNode", categoryNode);
        eq("planYear", planYear);

        return count();
    }

    public boolean hasNotZeroByCategoryNode(final CategoryNode categoryNode) {

        String hql = "select ditem from DisciplinePlanningItem as ditem "
                + "where ditem.categoryNode=:categoryNode "
                + "and ((ditem.plannedPlaces is not null and ditem.plannedPlaces<> 0)"
                + "or (ditem.actualEnrolment is not null and ditem.actualEnrolment<> 0)"
                + "or (ditem.plannedNew is not null and ditem.plannedNew<> 0)"
                + "or (ditem.plannedProgressing is not null and ditem.plannedProgressing<> 0))";
        log.info("hasNotZeroByCategoryNode : {}", hql);
        Query q = this.createQuery(hql);
        q.setParameter("categoryNode", categoryNode);

        List list = q.list();

        if (list.isEmpty()) {
            return false;
        } else {
            return true;
        }
    }
}
